package com.cancan.cloud.shop.utils;

import lombok.extern.slf4j.Slf4j;
import org.springframework.util.Assert;

import java.nio.charset.StandardCharsets;
import java.util.Base64;

/**
 * 权限模块，请求辅助类
 *
 * @author ZhangWei
 * @date 2020/12/8
 */
@Slf4j
public class AuthHeadHelper {

    public static final String SPLIT_CHARACTER = ":";

    public static final String SPLIT_SPACE = "\\s+";

    public static final String[] EMPTY_STRING_ARRAY = new String[]{};

    /**
     * 私有构造函数，避免工具类被实例化
     */
    private AuthHeadHelper() {
    }

    /**
     * 根据请求头部解析出系统ID
     *
     * @param header 请求头部字符串
     */
    public static Long parseClientId(String header) {
        Assert.notNull(header, "Authentication header must not be null.");
        String[] strings = parseAuthHeader(header);
        if (strings.length > 0 && StringUtils.isNumeric(strings[0])) {
            return Long.parseLong(strings[0]);
        }
        return null;
    }

    /**
     * 解析头部信息
     *
     * @param header header字符串
     */
    public static String[] parseAuthHeader(String header) {
        // 判断
        if (header == null || header.length() == 0) {
            return EMPTY_STRING_ARRAY;
        }
        // 从空格出进行分割
        String[] arr = header.split(SPLIT_SPACE);
        if (arr.length == 2 && (AuthScheme.BASIC.equalsIgnoreCase(arr[0]) || AuthScheme.DEVICE.equalsIgnoreCase(arr[0]))) {
            return decodeAuth(arr[1]);
        }
        return EMPTY_STRING_ARRAY;
    }

    /**
     * 解码请求头部认证字符串
     *
     * @param auth 要解码的header字符串
     * @return 解码后的字符串数组
     */
    public static String[] decodeAuth(String auth) {
        // 判断
        if (auth == null || auth.length() == 0) {
            return EMPTY_STRING_ARRAY;
        }
        // 解码
        try {
            byte[] bytes = auth.trim().getBytes(StandardCharsets.UTF_8);
            return new String(Base64.getDecoder().decode(bytes), StandardCharsets.UTF_8).split(SPLIT_CHARACTER);
        } catch (Exception e) {
            log.error("解码请求头部的认证字符串失败: {}", auth);
            return EMPTY_STRING_ARRAY;
        }
    }


    /**
     * 解析头部信息
     *
     * @param header header字符串
     */
    public static String extractSpnegoToken(String header) {
        // 判断
        if (header == null || header.length() == 0) {
            return null;
        }

        // 从空格出进行分割
        String[] arr = header.split(SPLIT_SPACE);
        if (arr.length == 2 && (AuthScheme.SPNEGO.equalsIgnoreCase(arr[0]) || AuthScheme.KERBEROS.equalsIgnoreCase(arr[0]))) {
            return arr[1];
        }
        return null;
    }
}
